package com.binance.mbxgateway.web.controller;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;

import com.binance.master.models.APIRequest;
import com.binance.master.models.APIRequest.VoidBody;
import com.binance.master.models.APIResponse;
import com.binance.mbxgateway.api.IMatchboxApi;
import com.binance.mbxgateway.vo.request.matchbox.DeleteApiKeyLockRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteApiKeyRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteApiKeyRuleRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteGasOptOutRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteIcebergPartsFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteLotSizeFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteMarketLotSizeFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteMinNotionalFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteNumAlgoOrdersFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteNumIcebergOrdersRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteNumOrdersFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteOpenOrdersRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteOrderRateLimitAccountRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteOrderRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeletePercentPriceFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeletePositionFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeletePriceFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteTPlusSellFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.DeleteUserDataStreamRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetAccountByExternalIdRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetAccountRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetAccountSymbolCommissionHistoryRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetAccountSymbolsCommissionRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetAccountTPlusLockStateRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetAllOrdersRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetApiKeyCheckRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetApiKeyLockRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetApiKeysRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetAssetBalanceRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetAssetLedgerRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetAuctionReportsRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetBalanceLedgerRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetCommissionRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetEstimateSymbolRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetFiltersRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetOpenOrdersRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetOrderRateLimitRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetOrderRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetSymbolCommissionHistoryRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetSymbolCommissionRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetSymbolHistoryRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetSymbolOrdersRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetTradesRequest;
import com.binance.mbxgateway.vo.request.matchbox.GetUserTradesRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostAccountRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostApiKeyRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostApiKeyRuleRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostAssetRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostBalanceRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostIcebergPartsFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostLotSizeFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostMarketLotSizeFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostMinNotionalFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostNumAlgoOrdersFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostNumIcebergOrdersRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostNumOrdersFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostOrderRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostPercentPriceFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostPositionFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostPriceFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostSymbolRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostTPlusSellFilterRequest;
import com.binance.mbxgateway.vo.request.matchbox.PostUserDataStreamRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutAccountAssetRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutAccountCommissionRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutAccountRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutAccountSymbolsCommissionRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutAllSymbolsRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutApiKeyLockRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutApiKeyPermissionsRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutExchangeGasRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutExchangeRateRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutGasOptOutRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutOrderRateLimitAccountRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutOrderRateLimitRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutOrderTypesRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutSymbolCommissionRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutSymbolCommissionTypeRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutSymbolRequest;
import com.binance.mbxgateway.vo.request.matchbox.PutUserDataStreamRequest;
import com.binance.mbxgateway.web.service.IMatchboxService;
import com.binance.mbxgateway.web.utils.MatchboxReturnUtils;

@RestController
public class MatchboxController implements IMatchboxApi {

    @Autowired
    private IMatchboxService matchboxService;

    @Override
    public APIResponse<String> getTime(@RequestBody @Validated APIRequest<VoidBody> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(this.matchboxService.getTime(), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getAllAccounts(@RequestBody @Validated APIRequest<VoidBody> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(this.matchboxService.getAllAccounts(), String.class);
        return APIResponse.getOKJsonResult(returnValue);
    }

    @Override
    public APIResponse<Void> putGasOptOut(@RequestBody @Validated APIRequest<PutGasOptOutRequest> request)
            throws Exception {
        this.matchboxService.putGasOptOut(request.getBody().getAccountId());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> putAccountAsset(@RequestBody @Validated APIRequest<PutAccountAssetRequest> request)
            throws Exception {
        this.matchboxService.putAccountAsset(request.getBody().getAccountId(), request.getBody().getAsset(),
                request.getBody().getAvailable(), request.getBody().getLocked(), request.getBody().getSymbolType());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getOpenOrders(@RequestBody @Validated APIRequest<GetOpenOrdersRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.getOpenOrders(request.getBody().getAccountId(), request.getBody().getSymbol()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deleteOpenOrders(@RequestBody @Validated APIRequest<DeleteOpenOrdersRequest> request)
            throws Exception {
        this.matchboxService.deleteOpenOrders(request.getBody().getAccountId(), request.getBody().getSymbol(),
                request.getBody().getForce());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> deleteGasOptOut(@RequestBody @Validated APIRequest<DeleteGasOptOutRequest> request)
            throws Exception {
        this.matchboxService.deleteGasOptOut(request.getBody().getAccountId());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getAllOrders(@RequestBody @Validated APIRequest<GetAllOrdersRequest> request)
            throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.getAllOrders(request.getBody().getAccountId(),
                        request.getBody().getEndTime(), request.getBody().getFromId(), request.getBody().getLimit(),
                        request.getBody().getStartTime(), request.getBody().getSymbol()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getAccount(@RequestBody @Validated APIRequest<GetAccountRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.getAccount(request.getBody().getAccountId()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getSymbolOrders(@RequestBody @Validated APIRequest<GetSymbolOrdersRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.getSymbolOrders(request.getBody().getSymbol(), request.getBody().getEndTime(),
                        request.getBody().getFromId(), request.getBody().getLimit(), request.getBody().getStartTime()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postAccount(@RequestBody @Validated APIRequest<PostAccountRequest> request)
            throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.postAccount(request.getBody().getExternalId(),
                        request.getBody().getBuyerCommission(), request.getBody().getCanDeposit(),
                        request.getBody().getCanTrade(), request.getBody().getCanWithdraw(),
                        request.getBody().getMakerCommission(), request.getBody().getSellerCommission(),
                        request.getBody().getTakerCommission()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> putAccount(@RequestBody @Validated APIRequest<PutAccountRequest> request)
            throws Exception {
        this.matchboxService.putAccount(request.getBody().getAccountId(), request.getBody().getCanDeposit(),
                request.getBody().getCanTrade(), request.getBody().getCanWithdraw());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getOrder(@RequestBody @Validated APIRequest<GetOrderRequest> request) throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.getOrder(request.getBody().getSymbol(),
                        request.getBody().getOrderId(), request.getBody().getOrigClientOrderId()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postOrder(@RequestBody @Validated APIRequest<PostOrderRequest> request)
            throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.postOrder(request.getBody().getAccountId(),
                        request.getBody().getQuantity(), request.getBody().getSide(), request.getBody().getSymbol(),
                        request.getBody().getType(), request.getBody().getForce(), request.getBody().getIcebergQty(),
                        request.getBody().getNewClientOrderId(), request.getBody().getNewOrderRespType(),
                        request.getBody().getPrice(), request.getBody().getStopPrice(),
                        request.getBody().getTargetOrderId(), request.getBody().getTimeInForce()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postBalance(@RequestBody @Validated APIRequest<PostBalanceRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.postBalance(request.getBody().getAccountId(), request.getBody().getAsset(),
                        request.getBody().getBalanceDelta(), request.getBody().getUpdateId()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deleteOrder(@RequestBody @Validated APIRequest<DeleteOrderRequest> request)
            throws Exception {
        this.matchboxService.deleteOrder(request.getBody().getAccountId(), request.getBody().getSymbol(),
                request.getBody().getForce(), request.getBody().getNewClientOrderId(), request.getBody().getOrderId(),
                request.getBody().getOrigClientOrderId());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getBalanceLedger(@RequestBody @Validated APIRequest<GetBalanceLedgerRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.getBalanceLedger(request.getBody().getAccountId(), request.getBody().getAsset(),
                        request.getBody().getEndTime(), request.getBody().getStartTime()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> putOrderTypes(@RequestBody @Validated APIRequest<PutOrderTypesRequest> request)
            throws Exception {
        this.matchboxService.putOrderTypes(request.getBody().getEnableIceberg(), request.getBody().getEnableMarket(),
                request.getBody().getEnableStopLoss(), request.getBody().getEnableStopLossLimit(),
                request.getBody().getEnableTakeProfit(), request.getBody().getEnableTakeProfitLimit(),
                request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> putApiKeyLock(@RequestBody @Validated APIRequest<PutApiKeyLockRequest> request)
            throws Exception {
        this.matchboxService.putApiKeyLock(request.getBody().getAccountId());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> putAllSymbols(@RequestBody @Validated APIRequest<PutAllSymbolsRequest> request)
            throws Exception {
        this.matchboxService.putAllSymbols(request.getBody().getSymbolStatus());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getTrades(@RequestBody @Validated APIRequest<GetTradesRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.getTrades(request.getBody().getSymbol(), request.getBody().getEndTime(),
                        request.getBody().getFromId(), request.getBody().getLimit(), request.getBody().getStartTime()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postApiKey(@RequestBody @Validated APIRequest<PostApiKeyRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.postApiKey(request.getBody().getAccountId(), request.getBody().getDesc(),
                        request.getBody().getCanAccessSecureWs(), request.getBody().getCanControlUserStreams(),
                        request.getBody().getCanTrade(), request.getBody().getCanViewMarketData(),
                        request.getBody().getCanViewUserData(), request.getBody().getForce()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getApiKeyCheck(@RequestBody @Validated APIRequest<GetApiKeyCheckRequest> request)
            throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.getApiKeyCheck(request.getBody().getApiKey(),
                        request.getBody().getIp(), request.getBody().getPayload(), request.getBody().getRecvWindow(),
                        request.getBody().getSignature(), request.getBody().getTimestamp()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deleteApiKey(@RequestBody @Validated APIRequest<DeleteApiKeyRequest> request)
            throws Exception {
        this.matchboxService.deleteApiKey(request.getBody().getAccountId(), request.getBody().getKeyId());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getAssets(@RequestBody @Validated APIRequest<VoidBody> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(this.matchboxService.getAssets(), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deleteApiKeyLock(@RequestBody @Validated APIRequest<DeleteApiKeyLockRequest> request)
            throws Exception {
        this.matchboxService.deleteApiKeyLock(request.getBody().getAccountId(), request.getBody().getRevert());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getCommission(@RequestBody @Validated APIRequest<GetCommissionRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.getCommission(request.getBody().getSymbol()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getApiKeyLock(@RequestBody @Validated APIRequest<GetApiKeyLockRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.getApiKeyLock(request.getBody().getAccountId()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deleteApiKeyRule(@RequestBody @Validated APIRequest<DeleteApiKeyRuleRequest> request)
            throws Exception {
        this.matchboxService.deleteApiKeyRule(request.getBody().getAccountId(), request.getBody().getKeyId(),
                request.getBody().getRuleId());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> postAsset(@RequestBody @Validated APIRequest<PostAssetRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.postAsset(request.getBody().getAsset(), request.getBody().getDecimalPlaces()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postSymbol(@RequestBody @Validated APIRequest<PostSymbolRequest> request)
            throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.postSymbol(request.getBody().getBaseAsset(),
                        request.getBody().getCommissionType(), request.getBody().getMaxPrice(),
                        request.getBody().getMaxQty(), request.getBody().getMinQty(), request.getBody().getQuoteAsset(),
                        request.getBody().getSymbol(), request.getBody().getSymbolType(),
                        request.getBody().getMatchingUnitType(), request.getBody().getMathSystemType()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getAssetBalance(@RequestBody @Validated APIRequest<GetAssetBalanceRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.getAssetBalance(request.getBody().getAsset()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> putExchangeRate(@RequestBody @Validated APIRequest<PutExchangeRateRequest> request)
            throws Exception {
        this.matchboxService.putExchangeRate(request.getBody().getBaseAsset(), request.getBody().getPrice(),
                request.getBody().getQuoteAsset(), request.getBody().getInvert());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getUserTrades(@RequestBody @Validated APIRequest<GetUserTradesRequest> request)
            throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.getUserTrades(request.getBody().getAccountId(),
                        request.getBody().getEndTime(), request.getBody().getFromId(), request.getBody().getLimit(),
                        request.getBody().getStartTime(), request.getBody().getSymbol()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getSymbolHistory(@RequestBody @Validated APIRequest<GetSymbolHistoryRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.getSymbolHistory(request.getBody().getStartTime(), request.getBody().getSymbol()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getFilters(@RequestBody @Validated APIRequest<GetFiltersRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.getFilters(request.getBody().getSymbol()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> putExchangeGas(@RequestBody @Validated APIRequest<PutExchangeGasRequest> request)
            throws Exception {
        this.matchboxService.putExchangeGas(request.getBody().getAsset(), request.getBody().getBips());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> putSymbol(@RequestBody @Validated APIRequest<PutSymbolRequest> request) throws Exception {
        this.matchboxService.putSymbol(request.getBody().getSymbol(), request.getBody().getSymbolStatus());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> postPriceFilter(@RequestBody @Validated APIRequest<PostPriceFilterRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.postPriceFilter(request.getBody().getMaxPrice(), request.getBody().getMinPrice(),
                        request.getBody().getSymbol(), request.getBody().getTickSize()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getApiKeys(@RequestBody @Validated APIRequest<GetApiKeysRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.getApiKeys(request.getBody().getAccountId()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postApiKeyRule(@RequestBody @Validated APIRequest<PostApiKeyRuleRequest> request)
            throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.postApiKeyRule(request.getBody().getAccountId(),
                        request.getBody().getIp(), request.getBody().getKeyId()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getSymbols(@RequestBody @Validated APIRequest<VoidBody> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(this.matchboxService.getSymbols(), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getAssetLedger(@RequestBody @Validated APIRequest<GetAssetLedgerRequest> request)
            throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.getAssetLedger(request.getBody().getAsset(),
                        request.getBody().getEndTime(), request.getBody().getStartTime()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postMinNotionalFilter(
            @RequestBody @Validated APIRequest<PostMinNotionalFilterRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.postMinNotionalFilter(request.getBody().getEnableMarket(),
                        request.getBody().getMinNotional(), request.getBody().getSymbol()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deletePercentPriceFilter(
            @RequestBody @Validated APIRequest<DeletePercentPriceFilterRequest> request) throws Exception {
        this.matchboxService.deletePercentPriceFilter(request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> putOrderRateLimit(@RequestBody @Validated APIRequest<PutOrderRateLimitRequest> request)
            throws Exception {
        this.matchboxService.putOrderRateLimit(request.getBody().getLimit(), request.getBody().getRateInterval());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> putApiKeyPermissions(
            @RequestBody @Validated APIRequest<PutApiKeyPermissionsRequest> request) throws Exception {
        this.matchboxService.putApiKeyPermissions(request.getBody().getAccountId(),
                request.getBody().getCanAccessSecureWs(), request.getBody().getCanControlUserStreams(),
                request.getBody().getCanTrade(), request.getBody().getCanViewMarketData(),
                request.getBody().getCanViewUserData(), request.getBody().getKeyId(), request.getBody().getForce());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getAccountTPlusLockState(
            @RequestBody @Validated APIRequest<GetAccountTPlusLockStateRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(this.matchboxService.getAccountTPlusLockState(
                request.getBody().getAccountId(), request.getBody().getSymbols()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postIcebergPartsFilter(
            @RequestBody @Validated APIRequest<PostIcebergPartsFilterRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(this.matchboxService
                .postIcebergPartsFilter(request.getBody().getLimit(), request.getBody().getSymbol()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deleteNumOrdersFilter(
            @RequestBody @Validated APIRequest<DeleteNumOrdersFilterRequest> request) throws Exception {
        this.matchboxService.deleteNumOrdersFilter(request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> deletePriceFilter(@RequestBody @Validated APIRequest<DeletePriceFilterRequest> request)
            throws Exception {
        this.matchboxService.deletePriceFilter(request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getAccountByExternalId(
            @RequestBody @Validated APIRequest<GetAccountByExternalIdRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.getAccountByExternalId(request.getBody().getExternalId()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postPercentPriceFilter(
            @RequestBody @Validated APIRequest<PostPercentPriceFilterRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.postPercentPriceFilter(request.getBody().getMultiplierDown(),
                        request.getBody().getMultiplierUp(), request.getBody().getSymbol()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getAccountSymbolsCommission(
            @RequestBody @Validated APIRequest<GetAccountSymbolsCommissionRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.getAccountSymbolsCommission(request.getBody().getAccountId()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> putUserDataStream(@RequestBody @Validated APIRequest<PutUserDataStreamRequest> request)
            throws Exception {
        this.matchboxService.putUserDataStream(request.getBody().getListenKey());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getOrderRateLimit(@RequestBody @Validated APIRequest<GetOrderRateLimitRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.getOrderRateLimit(request.getBody().getRateInterval()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getSymbolCommission(
            @RequestBody @Validated APIRequest<GetSymbolCommissionRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.getSymbolCommission(request.getBody().getSymbol()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getSymbolCommissionHistory(
            @RequestBody @Validated APIRequest<GetSymbolCommissionHistoryRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.getSymbolCommissionHistory(request.getBody().getEndTime(),
                        request.getBody().getStartTime(), request.getBody().getSymbol()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deleteTPlusSellFilter(
            @RequestBody @Validated APIRequest<DeleteTPlusSellFilterRequest> request) throws Exception {
        this.matchboxService.deleteTPlusSellFilter(request.getBody().getSymbol(), request.getBody().getForce());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> deleteMinNotionalFilter(
            @RequestBody @Validated APIRequest<DeleteMinNotionalFilterRequest> request) throws Exception {
        this.matchboxService.deleteMinNotionalFilter(request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> putAccountSymbolsCommission(
            @RequestBody @Validated APIRequest<PutAccountSymbolsCommissionRequest> request) throws Exception {
        this.matchboxService.putAccountSymbolsCommission(request.getBody().getAccountId(),
                request.getBody().getBuyerCommission(), request.getBody().getMakerCommission(),
                request.getBody().getSellerCommission(), request.getBody().getSymbols(),
                request.getBody().getTakerCommission());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> deletePositionFilter(
            @RequestBody @Validated APIRequest<DeletePositionFilterRequest> request) throws Exception {
        this.matchboxService.deletePositionFilter(request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> postNumIcebergOrders(
            @RequestBody @Validated APIRequest<PostNumIcebergOrdersRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.postNumIcebergOrders(request.getBody().getNumOrders(),
                        request.getBody().getSymbol(), request.getBody().getExemptAcct()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postUserDataStream(@RequestBody @Validated APIRequest<PostUserDataStreamRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.postUserDataStream(request.getBody().getAccountId()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> putSymbolCommissionType(
            @RequestBody @Validated APIRequest<PutSymbolCommissionTypeRequest> request) throws Exception {
        this.matchboxService.putSymbolCommissionType(request.getBody().getCommissionType(),
                request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> postNumAlgoOrdersFilter(
            @RequestBody @Validated APIRequest<PostNumAlgoOrdersFilterRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.postNumAlgoOrdersFilter(request.getBody().getNumOrders(),
                        request.getBody().getSymbol(), request.getBody().getExemptAcct()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getAuctionReports(@RequestBody @Validated APIRequest<GetAuctionReportsRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.getAuctionReports(request.getBody().getStartTime(), request.getBody().getSymbol()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postLotSizeFilter(@RequestBody @Validated APIRequest<PostLotSizeFilterRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.postLotSizeFilter(request.getBody().getMaxQty(), request.getBody().getMinQty(),
                        request.getBody().getStepSize(), request.getBody().getSymbol()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deleteOrderRateLimitAccount(
            @RequestBody @Validated APIRequest<DeleteOrderRateLimitAccountRequest> request) throws Exception {
        this.matchboxService.deleteOrderRateLimitAccount(request.getBody().getAccountId(),
                request.getBody().getRateInterval());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> deleteLotSizeFilter(@RequestBody @Validated APIRequest<DeleteLotSizeFilterRequest> request)
            throws Exception {
        this.matchboxService.deleteLotSizeFilter(request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> deleteNumAlgoOrdersFilter(
            @RequestBody @Validated APIRequest<DeleteNumAlgoOrdersFilterRequest> request) throws Exception {
        this.matchboxService.deleteNumAlgoOrdersFilter(request.getBody().getNumOrders(), request.getBody().getSymbol(),
                request.getBody().getExemptAcct());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getEstimateSymbol(@RequestBody @Validated APIRequest<GetEstimateSymbolRequest> request)
            throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.getEstimateSymbol(request.getBody().getBaseDecimalPlaces(),
                        request.getBody().getQuoteDecimalPlaces(), request.getBody().getMathSystemType(),
                        request.getBody().getMaxPrice(), request.getBody().getMaxQty()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> postNumOrdersFilter(
            @RequestBody @Validated APIRequest<PostNumOrdersFilterRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils
                .getMbxValue(this.matchboxService.postNumOrdersFilter(request.getBody().getNumOrders(),
                        request.getBody().getSymbol(), request.getBody().getExemptAcct()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deleteIcebergPartsFilter(
            @RequestBody @Validated APIRequest<DeleteIcebergPartsFilterRequest> request) throws Exception {
        this.matchboxService.deleteIcebergPartsFilter(request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> postMarketLotSizeFilter(
            @RequestBody @Validated APIRequest<PostMarketLotSizeFilterRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(
                this.matchboxService.postMarketLotSizeFilter(request.getBody().getMaxQty(),
                        request.getBody().getMinQty(), request.getBody().getStepSize(), request.getBody().getSymbol()),
                String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> deleteMarketLotSizeFilter(
            @RequestBody @Validated APIRequest<DeleteMarketLotSizeFilterRequest> request) throws Exception {
        this.matchboxService.deleteMarketLotSizeFilter(request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> deleteNumIcebergOrders(
            @RequestBody @Validated APIRequest<DeleteNumIcebergOrdersRequest> request) throws Exception {
        this.matchboxService.deleteNumIcebergOrders(request.getBody().getSymbol());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<Void> deleteUserDataStream(
            @RequestBody @Validated APIRequest<DeleteUserDataStreamRequest> request) throws Exception {
        this.matchboxService.deleteUserDataStream(request.getBody().getListenKey());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> postTPlusSellFilter(
            @RequestBody @Validated APIRequest<PostTPlusSellFilterRequest> request) throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.postTPlusSellFilter(request.getBody().getEndTime(),
                        request.getBody().getSymbol(), request.getBody().getExemptAcct()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> putOrderRateLimitAccount(
            @RequestBody @Validated APIRequest<PutOrderRateLimitAccountRequest> request) throws Exception {
        this.matchboxService.putOrderRateLimitAccount(request.getBody().getAccountId(), request.getBody().getLimit(),
                request.getBody().getRateInterval());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> postPositionFilter(@RequestBody @Validated APIRequest<PostPositionFilterRequest> request)
            throws Exception {
        String returnValue =
                MatchboxReturnUtils.getMbxValue(this.matchboxService.postPositionFilter(request.getBody().getMaxQty(),
                        request.getBody().getSymbol(), request.getBody().getExemptAcct()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> putSymbolCommission(@RequestBody @Validated APIRequest<PutSymbolCommissionRequest> request)
            throws Exception {
        this.matchboxService.putSymbolCommission(request.getBody().getBuyerCommission(),
                request.getBody().getMakerCommission(), request.getBody().getSellerCommission(),
                request.getBody().getSymbol(), request.getBody().getTakerCommission());
        return APIResponse.getOKJsonResult();

    }

    @Override
    public APIResponse<String> getCommands(@RequestBody @Validated APIRequest<VoidBody> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(this.matchboxService.getCommands(), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getPing(@RequestBody @Validated APIRequest<VoidBody> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(this.matchboxService.getPing(), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<String> getAccountSymbolCommissionHistory(
            @RequestBody @Validated APIRequest<GetAccountSymbolCommissionHistoryRequest> request) throws Exception {
        String returnValue = MatchboxReturnUtils.getMbxValue(this.matchboxService.getAccountSymbolCommissionHistory(
                request.getBody().getAccountId(), request.getBody().getEndTime(), request.getBody().getStartTime(),
                request.getBody().getSymbol()), String.class);
        return APIResponse.getOKJsonResult(returnValue);

    }

    @Override
    public APIResponse<Void> putAccountCommission(
            @RequestBody @Validated APIRequest<PutAccountCommissionRequest> request) throws Exception {
        this.matchboxService.putAccountCommission(request.getBody().getAccountId(),
                request.getBody().getBuyerCommission(), request.getBody().getMakerCommission(),
                request.getBody().getSellerCommission(), request.getBody().getTakerCommission());
        return APIResponse.getOKJsonResult();

    }
}
